using System;
using System.Collections.Generic;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Logging;
using Volo.Abp;
using Volo.Abp.Application.Dtos;
using Volo.Abp.AspNetCore.Mvc;
using UserManagementService.Organizations;
using UserManagementService.Permissions;
using UserManagementService.DTOs;

namespace UserManagementService.Organizations;

/// <summary>
/// 组织管理控制器
/// </summary>
[ApiController]
[Route("api/organizations")]
[Authorize]
public class OrganizationController : AbpControllerBase
{
    private readonly IOrganizationAppService _organizationAppService;
    private readonly ILogger<OrganizationController> _logger;

    public OrganizationController(
        IOrganizationAppService organizationAppService,
        ILogger<OrganizationController> logger)
    {
        _organizationAppService = organizationAppService;
        _logger = logger;
    }

    /// <summary>
    /// 获取组织列表
    /// </summary>
    [HttpGet]
    [Authorize(UserManagementPermissions.OrganizationPermissions.Default)]
    public async Task<PagedResultDto<OrganizationDto>> GetListAsync(SearchOrganizationsDto input)
    {
        try
        {
            return await _organizationAppService.GetListAsync(input);
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "获取组织列表失败");
            throw new UserFriendlyException("获取组织列表失败", ex.Message);
        }
    }

    /// <summary>
    /// 根据ID获取组织
    /// </summary>
    [HttpGet("{id}")]
    [Authorize(UserManagementPermissions.OrganizationPermissions.Default)]
    public async Task<OrganizationDto> GetAsync(Guid id)
    {
        try
        {
            return await _organizationAppService.GetAsync(id);
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "获取组织详情失败: {OrganizationId}", id);
            throw new UserFriendlyException("获取组织详情失败", ex.Message);
        }
    }

    /// <summary>
    /// 根据编码获取组织
    /// </summary>
    [HttpGet("by-code/{code}")]
    [Authorize(UserManagementPermissions.OrganizationPermissions.Default)]
    public async Task<OrganizationDto> GetByCodeAsync(string code)
    {
        try
        {
            return await _organizationAppService.GetByCodeAsync(code);
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "根据编码获取组织失败: {Code}", code);
            throw new UserFriendlyException("获取组织失败", ex.Message);
        }
    }

    /// <summary>
    /// 创建组织
    /// </summary>
    [HttpPost]
    [Authorize(UserManagementPermissions.OrganizationPermissions.Create)]
    public async Task<OrganizationDto> CreateAsync(CreateOrganizationDto input)
    {
        try
        {
            _logger.LogInformation("创建组织: {Code} - {Name}", input.Code, input.Name);
            return await _organizationAppService.CreateAsync(input);
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "创建组织失败: {Code} - {Name}", input.Code, input.Name);
            throw new UserFriendlyException("创建组织失败", ex.Message);
        }
    }

    /// <summary>
    /// 更新组织
    /// </summary>
    [HttpPut("{id}")]
    [Authorize(UserManagementPermissions.OrganizationPermissions.Edit)]
    public async Task<OrganizationDto> UpdateAsync(Guid id, UpdateOrganizationDto input)
    {
        try
        {
            _logger.LogInformation("更新组织: {OrganizationId}", id);
            return await _organizationAppService.UpdateAsync(id, input);
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "更新组织失败: {OrganizationId}", id);
            throw new UserFriendlyException("更新组织失败", ex.Message);
        }
    }

    /// <summary>
    /// 删除组织
    /// </summary>
    [HttpDelete("{id}")]
    [Authorize(UserManagementPermissions.OrganizationPermissions.Delete)]
    public async Task DeleteAsync(Guid id)
    {
        try
        {
            _logger.LogInformation("删除组织: {OrganizationId}", id);
            await _organizationAppService.DeleteAsync(id);
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "删除组织失败: {OrganizationId}", id);
            throw new UserFriendlyException("删除组织失败", ex.Message);
        }
    }

    /// <summary>
    /// 获取组织树
    /// </summary>
    [HttpGet("tree")]
    [Authorize(UserManagementPermissions.OrganizationPermissions.Default)]
    public async Task<List<OrganizationDto>> GetOrganizationTreeAsync([FromQuery] Guid? rootId = null)
    {
        try
        {
            return await _organizationAppService.GetTreeAsync(rootId);
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "获取组织树失败: {RootId}", rootId);
            throw new UserFriendlyException("获取组织树失败", ex.Message);
        }
    }

    /// <summary>
    /// 移动组织
    /// </summary>
    [HttpPost("{id}/move")]
    [Authorize(UserManagementPermissions.OrganizationPermissions.Manage)]
    public async Task<OrganizationDto> MoveOrganizationAsync(Guid id, [FromBody] MoveOrganizationDto input)
    {
        try
        {
            _logger.LogInformation("移动组织: {OrganizationId} 到 {NewParentId}", id, input.NewParentId);
            return await _organizationAppService.MoveOrganizationAsync(id, input);
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "移动组织失败: {OrganizationId}", id);
            throw new UserFriendlyException("移动组织失败", ex.Message);
        }
    }

    /// <summary>
    /// 启用组织
    /// </summary>
    [HttpPost("{id}/enable")]
    [Authorize(UserManagementPermissions.OrganizationPermissions.Manage)]
    public async Task<OrganizationDto> EnableOrganizationAsync(Guid id)
    {
        try
        {
            _logger.LogInformation("启用组织: {OrganizationId}", id);
            return await _organizationAppService.EnableOrganizationAsync(id);
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "启用组织失败: {OrganizationId}", id);
            throw new UserFriendlyException("启用组织失败", ex.Message);
        }
    }

    /// <summary>
    /// 禁用组织
    /// </summary>
    [HttpPost("{id}/disable")]
    [Authorize(UserManagementPermissions.OrganizationPermissions.Manage)]
    public async Task<OrganizationDto> DisableOrganizationAsync(Guid id)
    {
        try
        {
            _logger.LogInformation("禁用组织: {OrganizationId}", id);
            return await _organizationAppService.DisableOrganizationAsync(id);
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "禁用组织失败: {OrganizationId}", id);
            throw new UserFriendlyException("禁用组织失败", ex.Message);
        }
    }

    /// <summary>
    /// 获取组织成员
    /// </summary>
    [HttpGet("{id}/members")]
    [Authorize(UserManagementPermissions.OrganizationPermissions.ViewMembers)]
    public async Task<PagedResultDto<OrganizationMemberDto>> GetMembersAsync(
        Guid id,
        PagedAndSortedResultRequestDto input)
    {
        try
        {
            return await _organizationAppService.GetMembersAsync(id, input);
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "获取组织成员失败: {OrganizationId}", id);
            throw new UserFriendlyException("获取组织成员失败", ex.Message);
        }
    }

    /// <summary>
    /// 添加组织成员
    /// </summary>
    [HttpPost("{id}/members")]
    [Authorize(UserManagementPermissions.OrganizationPermissions.ManageMembers)]
    public async Task<OrganizationMemberDto> AddMemberAsync(Guid id, [FromBody] AddOrganizationMemberDto input)
    {
        try
        {
            _logger.LogInformation("添加组织成员: {OrganizationId} - {UserId}", id, input.UserId);
            return await _organizationAppService.AddMemberAsync(id, input);
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "添加组织成员失败: {OrganizationId} - {UserId}", id, input.UserId);
            throw new UserFriendlyException("添加组织成员失败", ex.Message);
        }
    }

    /// <summary>
    /// 更新组织成员
    /// </summary>
    [HttpPut("{id}/members/{userId}")]
    [Authorize(UserManagementPermissions.OrganizationPermissions.ManageMembers)]
    public async Task<OrganizationMemberDto> UpdateMemberAsync(Guid id, Guid userId, [FromBody] UpdateOrganizationMemberDto input)
    {
        try
        {
            _logger.LogInformation("更新组织成员: {OrganizationId} - {UserId}", id, userId);
            return await _organizationAppService.UpdateMemberAsync(id, userId, input);
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "更新组织成员失败: {OrganizationId} - {UserId}", id, userId);
            throw new UserFriendlyException("更新组织成员失败", ex.Message);
        }
    }

    /// <summary>
    /// 移除组织成员
    /// </summary>
    [HttpDelete("{id}/members/{userId}")]
    [Authorize(UserManagementPermissions.OrganizationPermissions.ManageMembers)]
    public async Task RemoveMemberAsync(Guid id, Guid userId)
    {
        try
        {
            _logger.LogInformation("移除组织成员: {OrganizationId} - {UserId}", id, userId);
            await _organizationAppService.RemoveMemberAsync(id, userId);
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "移除组织成员失败: {OrganizationId} - {UserId}", id, userId);
            throw new UserFriendlyException("移除组织成员失败", ex.Message);
        }
    }

    /// <summary>
    /// 获取组织统计信息
    /// </summary>
    [HttpGet("statistics")]
    [Authorize(UserManagementPermissions.OrganizationPermissions.Default)]
    public async Task<OrganizationStatisticsDto> GetStatisticsAsync([FromQuery] Guid? organizationId = null)
    {
        try
        {
            return await _organizationAppService.GetStatisticsAsync(organizationId);
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "获取组织统计信息失败: {OrganizationId}", organizationId);
            throw new UserFriendlyException("获取统计信息失败", ex.Message);
        }
    }

    /// <summary>
    /// 搜索组织
    /// </summary>
    [HttpPost("search")]
    [Authorize(UserManagementPermissions.OrganizationPermissions.Default)]
    public async Task<List<OrganizationDto>> SearchOrganizationsAsync([FromBody] SearchOrganizationsDto input)
    {
        try
        {
            return await _organizationAppService.SearchOrganizationsAsync(input);
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "搜索组织失败: {Keyword}", input.Keyword);
            throw new UserFriendlyException("搜索组织失败", ex.Message);
        }
    }

    /// <summary>
    /// 导入组织
    /// </summary>
    [HttpPost("import")]
    [Authorize(UserManagementPermissions.OrganizationPermissions.Import)]
    public async Task<OrganizationImportResultDto> ImportOrganizationsAsync([FromBody] ImportOrganizationsDto input)
    {
        try
        {
            _logger.LogInformation("导入组织: {Count} 个", input.Organizations.Count);
            return await _organizationAppService.ImportOrganizationsAsync(input);
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "导入组织失败");
            throw new UserFriendlyException("导入组织失败", ex.Message);
        }
    }

    /// <summary>
    /// 导出组织
    /// </summary>
    [HttpPost("export")]
    [Authorize(UserManagementPermissions.OrganizationPermissions.Export)]
    public async Task<FileResultDto> ExportOrganizationsAsync([FromBody] ExportOrganizationsDto input)
    {
        try
        {
            _logger.LogInformation("导出组织");
            return await _organizationAppService.ExportOrganizationsAsync(input);
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "导出组织失败");
            throw new UserFriendlyException("导出组织失败", ex.Message);
        }
    }
}